//GGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGG
// EdgePrcs.h		header file
//
// Author:			Cheng-en Guo
//
// Created Time:	07-15-99
// Revised Time:
//
// Descriptions:	This file is to define the class to do edge processing.
//					Including filter, edge detection, build the edge map, and segment by edges
//
// Member variables:
//
// Functions:
//
//GGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGG
#ifndef _EDGEPRCS_H_
#define _EDGEPRCS_H_

#define LEVEL_NUM 1
#define REGION_NUM 2

#include "CgEdgeLinking.h"
#include "mcEdgeOp.h"


class CEdgePrcs
{
public:
	CEdgePrcs();
	~CEdgePrcs();
	void	SetDimension(int nHeight, int nWidth);

	int LabelRegions(double dSigma, mcmcMatrix<int> &mx_region_labels, bool bColor, Raster_Color<uchar> *praster_color);

	void SetColor( int nColor ) { m_nColor = nColor; }

	double GetSigma() const { return m_dSigma; }
	void SetSigma( double dSigma ) { m_dSigma = dSigma; }

	int SetPecentThreshHi( int i, double* pd );
	int SetPecentThreshLo( int i, double* pd );
	int SetStrengthThreshHi( int i, double* pd );
	int SetStrengthThreshLo( int i, double* pd );
	int SetMinContourLength( int l ) { m_nMinContourLength = l; return l; }
	int SetMaxContourLength( int l ) { m_nMaxContourLength = l; return l; }
	int SegmentRegions(Raster_Color<uchar> &raster_color);
	int LabelRegions( mcmcMatrix<BYTE>& BMarixEdge, mcmcMatrix<int> & MatrixRegionLabels, int& nLableNo );
	int	LabelRegionFromOneSeed( int x, int y, mcmcMatrix<BYTE>* pBMatrixEdge, mcmcMatrix<int>* pMatrixRegionLabels, int nLabelNo, CGPoint* pPoints );

	int GetRegionNum() { return m_nRegionNum; }
	int Sign( int n )
	{
		if( n > 0 )
			return 1;
		else if( n < 0 )
			return -1;
		else
			return 0;
	}


private:
	void	Initialize();
	int		InitializeOtherVariables();
	int		EdgeDetectionWithEigenvector(Raster_Color<uchar> *praster_color=NULL);

	double	FindPercentThreshold( mcmcMatrix<float> *pFM, double fTh );
	int		GetStrengthThreshFromPercentThresh();
	BOOL	EdgeLocalMax( int ax, int ay, mcmcMatrix<float> *pFMEdgeStrength, mcmcMatrix<float> *pFMEdgeX, mcmcMatrix<float> *pFMEdgeY, double fTh );
	int		GetEdgeLocalMax();
	void	GetContourAtOnePoint4OverSegment(int nLevel,CGPoint p,CContour *pNewContour,double fThreshHi,double fThreshLo,	int nFlag);
	int		TraceContour4OverSegment( int nLevel, int end, CContour *pContour, double fThreshHi, double fThreshLo, int nFlag );
	void	SetPointer2ContourMatrix( CContour *pContour, SPCMatrix *pPCMatrix, BOOL flag );
	int		GetDirectionFromAngle( float fAngle );
	BOOL	Direction2Vector( int nDir, CFVector *pV );
	CGPoint Direction2Point( int nDir );
	float	Compatible( CFVector &v, CFVector &v1, CFVector &v2 );
	float	CalculateContourAverageEdgeStrength( CContour *pCon, mcmcMatrix<float> *pFMEdgeSt );
	void	FindNeighborMovingPoints( CGPoint p, int &n, CGPoint &p1, CGPoint &p2, CGPoint &p3 );
	float	CalculateContinuityStrength( CContour *pC1, int &nEnd1, CContour *pC2, int &nEnd2, CGPoint p );
	bool	PointsNeighborJudge( CGPoint p1, CGPoint p2 );
	int		SetBMatrixFlagOfPointList( mcmcMatrix<BYTE>& BMatrixFlag, CGPointList& PointList, BYTE bValue );
	bool	ContourCrossSegLine( CContour& LinkContour, mcmcMatrix<BYTE>& BMatrixOnSegLineFlag );
	int		BuildContourList4OverSegment( int l );
	int		De_freeTheEndsOfAllContours( int l );
	int		CutContour( CContour* pContour, CGPoint p1, int end, int nLevel );
	int		CombineContour( CContour* pC1, int end1, CContour* pC2, int end2, int nLevel, int nDelete );
	int		BuildContourMap4OverSegment(int nLevel, int nFlag);
	int		GetNeighborsOfAContourAtOneEnd( CContour* pCurContour, int nLevel, int nFlag, int nEnd );
	CGPoint MovePointIntoRegion( CGPoint ptN, int nWidth, int nHeight );

	int		DirectExtendContourUntilNoneFree( CContour* pCurContour, int nLevel, int end );
	float	GetAngleFromDirection( float fAngle, int nDir );
	int		De_freeOneEndOfOneContour( CContour* pCurContour, CContour* pContourAlreadyLinked, int nEnd, int nLevel );
	void	LabelBoundaries(mcmcMatrix<int> *pMatrixRegionLabels);


public:
	mcmcMatrix<int>		m_MatrixRegionLabels;

private:
	int m_nRegionNum;

	CContour*		m_pContour;
	CContour*		m_pCurContour;
	CContour		m_ContourRepresentBoudary;
	int m_ppnSearchDirection[9][9];
	CGPoint m_pGPointNeighbor[8];

	int				m_nColor;//0-gray, 1-color
	int				m_nRawImageWidth;// the width of raw image
	int				m_nRawImageHeight; // the height of raw image

	mcmcMatrix<float>	m_FMatrixEdgeStrength;// the float matrix of the edge strength
	mcmcMatrix<float>	m_FMatrixEdgeX;// the float matrix of the edge strength in x direction
	mcmcMatrix<float>	m_FMatrixEdgeY;// the float matrix of the edge strength in y direction
	mcmcMatrix<float>	m_FMatrixEdgeAngle;// the float matrix of the edge angle
	SPCMatrix		m_PMatrixContour;// the pointer matrix to contour
	mcmcMatrix<BYTE>	m_pBMatrixLocalMax[LEVEL_NUM];// local max matrix for all the level
	mcmcMatrix<BYTE>	m_pBMatrixLocalMax0[LEVEL_NUM];// local max matrix for all the level for cross judge
	mcmcMatrix<BYTE>	m_pBMatrixOverSegmentLines[LEVEL_NUM];//over segment boundary for all the level
	mcmcMatrix<BYTE>	m_BMatrixLocalMaxFlag;// the matrix to show which level this point is in
	mcmcMatrix<BYTE>	m_BMatrixRegionFlag;// the matrix indicates which points are in the region
	double			m_pdPercentThreshHi[LEVEL_NUM];// hi percent threshold of edge strength
	double			m_pdPercentThreshLo[LEVEL_NUM];// low percent threshold of edge strength
	double			m_pdStrengthThreshHi[LEVEL_NUM];// hi hreshold of edge strength
	double			m_pdStrengthThreshLo[LEVEL_NUM];// hi threshold of edge strength
	CContourList	m_pContourListWholeImage[LEVEL_NUM];// the contour list of the whole image, LEVEL_NUM levels

	double			m_dSigma;
	int				m_nMinContourLength;
	int				m_nMaxContourLength;
};

#endif //_EDGEPRCS_H_
